﻿#region 命名空间

using System;
using System.Collections.Generic;
using System.Collections.Specialized;
using System.Linq;
using System.Reflection;
using System.Text;
using Microsoft.Practices.EnterpriseLibrary.Common.Configuration;
using Microsoft.Practices.Unity.InterceptionExtension;

#endregion

namespace Sharp.Infrastructure.Crosscutting
{
    /// <summary>
    ///     异常的处理类
    /// </summary>
    [ConfigurationElementType(typeof (CustomCallHandlerData))]
    public class ExceptionCallHandler : ICallHandler
    {
        /// <summary>
        ///     异常的处理类
        /// </summary>
        /// <param name="order"></param>
        public ExceptionCallHandler(int order)
        {
            Order = order;
        }

        /// <summary>
        ///     构造函数，此处不可省略，否则会导致异常
        /// </summary>
        /// <param name="attributes">配置文件中所配置的参数</param>
        public ExceptionCallHandler(NameValueCollection attributes)
        {
            Order = Convert.ToInt32(attributes["Order"]);
        }

        /// <summary>
        ///     排序
        /// </summary>
        public int Order { get; set; }

        /// <summary>
        ///     执行
        /// </summary>
        /// <param name="input"></param>
        /// <param name="getNext"></param>
        /// <returns></returns>
        public IMethodReturn Invoke(IMethodInvocation input, GetNextHandlerDelegate getNext)
        {
            var result = getNext().Invoke(input, getNext);

            if (result.Exception != null)
            {
                if (((MethodInfo) (input.MethodBase)).ReturnType == typeof (Result))
                {
                    if (result.Exception.GetType().FullName.Contains("DbEntityValidationException"))
                    {
                        dynamic err = result.Exception;
                        IEnumerable<dynamic> list = err.EntityValidationErrors;

                        StringBuilder errInfos = new StringBuilder();
                        list.ToList().ForEach(x => { errInfos.AppendLine(x.ValidationErrors); });
                        //LogHelper.Error(err);
                    }
                    else
                    {
                        //LogHelper.Error(result.Exception);
                    }

                    Result res = new Result
                    {
                        Err = result.Exception.Message
                    };

                    return input.CreateMethodReturn(res, new object[] {input.Arguments});
                }

                //ExceptionPolicy.HandleException(ex, this.PolicyName);

                //LogHelper.Error(result.Exception);
                throw result.Exception;
            }
            return result;
        }
    }
}